package com.gibbs.gplayer;

import android.media.AudioFormat;
import android.media.MediaCodecList;
import android.media.MediaFormat;
import android.util.ArrayMap;
import android.util.Log;

import java.util.Map;

import static android.media.MediaCodecList.REGULAR_CODECS;

public class CommonUtil {
    private static final String TAG = "CommonUtil";

    /**
     * ffmpeg sample fmt
     */
    private static final int FFMPEG_SAMPLE_FMT_U8 = 0;          ///< unsigned 8 bits
    private static final int FFMPEG_SAMPLE_FMT_S16 = 1;         ///< signed 16 bits
    private static final int FFMPEG_SAMPLE_FMT_S32 = 2;         ///< signed 32 bits
    private static final int FFMPEG_SAMPLE_FMT_FLT = 3;         ///< float
    private static final int FFMPEG_SAMPLE_FMT_DBL = 4;         ///< double
    private static final int FFMPEG_SAMPLE_FMT_U8P = 5;         ///< unsigned 8 bits, planar
    private static final int FFMPEG_SAMPLE_FMT_S16P = 6;        ///< signed 16 bits, planar
    private static final int FFMPEG_SAMPLE_FMT_S32P = 7;        ///< signed 32 bits, planar
    private static final int FFMPEG_SAMPLE_FMT_FLTP = 8;        ///< float, planar
    private static final int FFMPEG_SAMPLE_FMT_DBLP = 9;        ///< double, planar
    private static final int FFMPEG_SAMPLE_FMT_S64 = 10;        ///< signed 64 bits
    private static final int FFMPEG_SAMPLE_FMT_S64P = 11;       ///< signed 64 bits, planar

    private static final Map<Integer, Integer> sSampleFmtMap = new ArrayMap<>();
    private static final Map<Integer, Integer> sChannelFmtMap = new ArrayMap<>();

    static {
        sChannelFmtMap.put(1, AudioFormat.CHANNEL_OUT_MONO);
        sChannelFmtMap.put(2, AudioFormat.CHANNEL_OUT_STEREO);
        sChannelFmtMap.put(3, AudioFormat.CHANNEL_OUT_SURROUND);
        sChannelFmtMap.put(4, AudioFormat.CHANNEL_OUT_QUAD);
        sChannelFmtMap.put(6, AudioFormat.CHANNEL_OUT_5POINT1);

        sSampleFmtMap.put(FFMPEG_SAMPLE_FMT_U8, AudioFormat.ENCODING_PCM_8BIT);
        sSampleFmtMap.put(FFMPEG_SAMPLE_FMT_S16, AudioFormat.ENCODING_PCM_16BIT);
        sSampleFmtMap.put(FFMPEG_SAMPLE_FMT_FLTP, AudioFormat.ENCODING_PCM_FLOAT);
    }

    //call by jni
    public static String findDecoderForFormat(String formatInfo) {
        MediaCodecList mediaCodecList = new MediaCodecList(REGULAR_CODECS);
        MediaFormat mediaFormat = new MediaFormat();
        mediaFormat.setString(MediaFormat.KEY_MIME, formatInfo);
        String codecName = mediaCodecList.findDecoderForFormat(mediaFormat);
        Log.i(TAG, "findDecoderForFormat " + formatInfo + "==>" + codecName);
        return codecName;
    }

    public static int getFfmpegSampleFmt(int mediaCodecFmt) {
        for(Map.Entry<Integer, Integer> entry : sSampleFmtMap.entrySet()){
            if (mediaCodecFmt == entry.getValue()) {
                return entry.getKey();
            }
        }

        Log.e(TAG, "can not find ffmpeg fmt for mediaCodecFmt " + mediaCodecFmt);
        return mediaCodecFmt;
    }

    public static int getMediaCodecSampleFmt(int ffmpegFmt) {
        if (sSampleFmtMap.containsKey(ffmpegFmt)) {
            return sSampleFmtMap.get(ffmpegFmt);
        }

        Log.e(TAG, "can not find mediaCodec fmt for ffmpegFmt " + ffmpegFmt);
        return ffmpegFmt;
    }

    public static int getChannelLayout(int channels) {
        return sChannelFmtMap.get(channels);
    }
}
